package cn.zhouchao.filter;

import com.alibaba.fastjson.JSON;
import com.netflix.zuul.ZuulFilter;
import com.netflix.zuul.context.RequestContext;
import com.netflix.zuul.exception.ZuulException;
import lombok.SneakyThrows;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;

import javax.servlet.http.HttpServletResponse;
import java.io.PrintWriter;
import java.util.HashMap;
import java.util.Map;

@Component
public class LoginCheckFilter extends ZuulFilter {
    /**
     * 通过返回的字符串指定过滤器类型（前置，路由，后置，异常）
     * @return
     */
    @Override
    public String filterType() {
        return "pre";
    }
    /**
     * 过滤器执行时机，数字越小越优先执行（这里我们就用就可以了，当然-1也行）
     * @return
     */
    @Override
    public int filterOrder() {
        return 0;
    }

    /**
     * 判断要不要执行下面的run方法(返回true走，false不走)
     * @return
     */
    @Override
    public boolean shouldFilter() {
        // 将请求和响应装在一个对象当中，就可以用通过这个对象来取
        // url是请求的全路径，包括ip+port...  uri是只有路径
        // 1.判断是否访问的是公共路径
        RequestContext context = RequestContext.getCurrentContext();
        String uri = context.getRequest().getRequestURI();
        // 判断是否是登录或者是注册，是的话就放行，即不走run方法
        if (uri.endsWith("Login") || uri.endsWith("register")) {
            return false;
        }
        // 否者，如果访问的不是公共路径就需要进行登录校验
        return true;
    }

    /**
     * 执行当前过滤器的核心业务
     * @return
     * @throws ZuulException
     */
    @SneakyThrows //
    @Override
    public Object run() throws ZuulException {
        // 做登录校验
        // 1.获取token
        RequestContext context = RequestContext.getCurrentContext();
        String token = context.getRequest().getHeader("token"); // 获取请求，从总获取请求头当中的token
        // 2.判断是否登录（）
        if (StringUtils.isEmpty("token")) { // 如果token为空，就判定没有登录，就返回提示
            Map<String, Object> map = new HashMap<>(); // 创建一个HashMap用父类Map来接受的对象，
            map.put("message", "请登录");
            map.put("success", "false");
            map.put("obje", "noLogin");
            String jsonString = JSON.toJSONString(map); // 利用阿里的fastjson，将map对象转换为json字符串
            HttpServletResponse response = context.getResponse(); // 调用响应对象
            response.setContentType("application/json;charset=UTF-8"); // 设置返回响应为json格式，以及字符集
            PrintWriter writer = response.getWriter(); // 通过在方法上加注解@SneakyThrows解决报错，或者点more的try catch
            writer.write(jsonString);
            // 因为没登录，所以走完前置，不走异常，直接响应给前端
            context.setSendZuulResponse(false);
            writer.close(); // 关流，不然就会多出来，导致报错
        }
        // 返回什么都会被忽略，所以咱返回一个true
        return true;
    }
}
